package com.yunke.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.yunke.entity.YunkeTag;
import com.yunke.mapper.YunkeTagMapper;
import com.yunke.service.YunkeTagService;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import java.util.List;

/**
 * 标签管理服务实现类
 * 
 * @author yunke
 * @since 1.0.0
 */
@Slf4j
@Service
@RequiredArgsConstructor
public class YunkeTagServiceImpl extends ServiceImpl<YunkeTagMapper, YunkeTag> implements YunkeTagService {

    private final YunkeTagMapper yunkeTagMapper;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean createTag(YunkeTag tag) {
        try {
            // 检查标签编码是否存在
            if (StringUtils.hasText(tag.getTagCode())) {
                LambdaQueryWrapper<YunkeTag> wrapper = new LambdaQueryWrapper<>();
                wrapper.eq(YunkeTag::getTagCode, tag.getTagCode())
                       .eq(YunkeTag::getStatus, 0);
                if (this.count(wrapper) > 0) {
                    throw new RuntimeException("标签编码已存在");
                }
            }

            // 设置默认值
            tag.setUseCount(0);
            tag.setHotWeight(0);
            tag.setSortWeight(0);
            tag.setIsHot(false);
            tag.setIsRecommend(false);
            tag.setIsEnabled(true);
            tag.setStatus(0);
            tag.setCreateTime(System.currentTimeMillis());
            tag.setUpdateTime(System.currentTimeMillis());

            return this.save(tag);
        } catch (Exception e) {
            log.error("创建标签失败", e);
            throw new RuntimeException("创建标签失败：" + e.getMessage());
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean updateTag(YunkeTag tag) {
        try {
            // 检查标签是否存在
            YunkeTag existingTag = this.getById(tag.getId());
            if (existingTag == null || existingTag.getStatus() == 1) {
                throw new RuntimeException("标签不存在");
            }

            // 检查标签编码是否重复
            if (StringUtils.hasText(tag.getTagCode()) && !tag.getTagCode().equals(existingTag.getTagCode())) {
                LambdaQueryWrapper<YunkeTag> wrapper = new LambdaQueryWrapper<>();
                wrapper.eq(YunkeTag::getTagCode, tag.getTagCode())
                       .eq(YunkeTag::getStatus, 0)
                       .ne(YunkeTag::getId, tag.getId());
                if (this.count(wrapper) > 0) {
                    throw new RuntimeException("标签编码已存在");
                }
            }

            tag.setUpdateTime(System.currentTimeMillis());
            return this.updateById(tag);
        } catch (Exception e) {
            log.error("更新标签失败", e);
            throw new RuntimeException("更新标签失败：" + e.getMessage());
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean deleteTag(Long id) {
        try {
            YunkeTag tag = this.getById(id);
            if (tag == null) {
                throw new RuntimeException("标签不存在");
            }

            tag.setStatus(1);
            tag.setUpdateTime(System.currentTimeMillis());
            return this.updateById(tag);
        } catch (Exception e) {
            log.error("删除标签失败", e);
            throw new RuntimeException("删除标签失败：" + e.getMessage());
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean deleteTags(List<Long> ids) {
        try {
            for (Long id : ids) {
                this.deleteTag(id);
            }
            return true;
        } catch (Exception e) {
            log.error("批量删除标签失败", e);
            throw new RuntimeException("批量删除标签失败：" + e.getMessage());
        }
    }

    @Override
    public IPage<YunkeTag> getTagPage(Integer current, Integer size, String tagName, 
                                     Integer tagType, String tagCategory, Boolean isEnabled) {
        Page<YunkeTag> page = new Page<>(current, size);
        return yunkeTagMapper.selectTagPage(page, tagName, tagType, tagCategory, isEnabled);
    }

    @Override
    public YunkeTag getTagById(Long id) {
        LambdaQueryWrapper<YunkeTag> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(YunkeTag::getId, id)
               .eq(YunkeTag::getStatus, 0);
        return this.getOne(wrapper);
    }

    @Override
    public List<YunkeTag> getTagsByType(Integer tagType, Boolean isEnabled) {
        return yunkeTagMapper.selectByType(tagType, isEnabled, null);
    }

    @Override
    public List<YunkeTag> getTagsByCategory(String tagCategory, Boolean isEnabled) {
        return yunkeTagMapper.selectByCategory(tagCategory, isEnabled, null);
    }

    @Override
    public List<YunkeTag> getHotTags(Integer limit) {
        return yunkeTagMapper.selectHotTags(limit);
    }

    @Override
    public List<YunkeTag> getRecommendTags(Integer limit) {
        return yunkeTagMapper.selectRecommendTags(limit);
    }

    @Override
    public List<YunkeTag> searchTags(String keyword, Integer limit) {
        return yunkeTagMapper.searchTags(keyword, limit);
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean enableTag(Long id) {
        return yunkeTagMapper.updateTagStatus(id, true) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean disableTag(Long id) {
        return yunkeTagMapper.updateTagStatus(id, false) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean setHot(Long id) {
        return yunkeTagMapper.updateHotStatus(id, true) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean cancelHot(Long id) {
        return yunkeTagMapper.updateHotStatus(id, false) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean setRecommend(Long id) {
        return yunkeTagMapper.updateRecommendStatus(id, true) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean cancelRecommend(Long id) {
        return yunkeTagMapper.updateRecommendStatus(id, false) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean increaseUseCount(Long id) {
        return yunkeTagMapper.incrementUseCount(id) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean increaseUseCount(List<Long> ids) {
        return yunkeTagMapper.batchIncrementUseCount(ids) > 0;
    }

    @Override
    public long countTags(Integer tagType, String tagCategory, Boolean isEnabled) {
        return yunkeTagMapper.countTags(tagType, tagCategory, isEnabled);
    }

    @Override
    public List<String> getAllCategories() {
        return yunkeTagMapper.selectAllCategories();
    }
} 